/**
 * 文件名称: main.c
 * 摘    要: linux应用程序下操作gpio测试
 * 来    源: 参考 http://bbs.myir-tech.com/thread-7183-1-1.html
 *
 * 当前版本: 1.0 
 * 作    者: huenrong
 * 完成日期: 2019年05月12日
 **/

#include<stdio.h>
#include <stdlib.h>
#include<sys/types.h>
#include<sys/stat.h>
#include<fcntl.h>
#include<unistd.h>
#include<errno.h>
#include<string.h>
#include <poll.h>

#include "gpio.h"


#define     GPIO_K3     128
#define     GPIO_D30    129
#define     POLL_TIMEOUT (3 * 1000) /* 3 seconds */
#define MAX_BUF 60

int main(int argc, char **argv)
{
    int ret = -1;       // 函数返回值
    int gpio_value = -1;        // 获取到的gpio值
    int gpio_value_new = -1;    // 获取到的gpio值
    int gpio_fd = -1;
    struct pollfd *fdset;
    int timeout = -1;
    char *buf[MAX_BUF];

    fdset = (struct pollfd*)malloc(sizeof(struct pollfd));

    // 导出需要操作的gpio
    gpio_export(GPIO_K3);       // 导出编号为128的gpio(米尔MYB-Y6ULX开发板K3 按键)
    gpio_export(GPIO_D30);      // 导出编号为129的gpio(米尔MYB-Y6ULX开发板D30 blue LED)

    // 配置gpio方向
    gpio_set_direction(GPIO_K3, IN);
    gpio_set_direction(GPIO_D30, OUT);

    // 配置按键为中断模式(下降沿)
    gpio_set_edge(GPIO_K3, "falling");
    gpio_fd = gpio_fd_open(GPIO_K3);

    timeout = POLL_TIMEOUT;

    // 按下按键D30点亮, 释放按键D30熄灭
    while (0)
    {
        ret = -1;
        ret = gpio_get_value(GPIO_K3, &gpio_value);
        if (0 == ret)
        {
            usleep(50 * 1000);      // 延时消抖

            ret = gpio_get_value(GPIO_K3, &gpio_value_new);
            if ((0 == ret) && (gpio_value_new == gpio_value))
            {
                if (0 == gpio_value)
                {
                    printf("Press the K3 button!\r\n");
                    gpio_set_value(GPIO_D30, 0);
                }
                else
                {
                    // printf("Release K3 button\r\n");
                    gpio_set_value(GPIO_D30, 1);
                }
            }
        }
    }

    while (1)
    {
        memset(fdset, 0, sizeof(fdset));
        fdset->fd = gpio_fd;
        fdset->events = POLLPRI;

        ret = poll(fdset, 1, timeout);

        if (ret < 0)
        {
            printf("\npoll() failed!\n");  
            
            return -1;  
        }  
            
        if (ret == 0)
        {
            printf(".");
        }

        // 这里不知道为什么程序第一次运行时会产生中断       
        if (fdset->revents & POLLPRI)
        {
            lseek(fdset->fd, 0, SEEK_SET);  // Read from the start of the file
            read(fdset->fd, buf, MAX_BUF);  
            usleep(50 * 000);
            printf("\nK3 interrupt occurred\n");

            gpio_get_value(GPIO_K3, &gpio_value);

            if (0 == gpio_value)
            {
                printf("Press the K3 button!\r\n");
                gpio_set_value(GPIO_D30, 0);
            }
            else
            {
                // printf("Release K3 button\r\n");
                gpio_set_value(GPIO_D30, 1);
            }
        }

        fflush(stdout);
    }

    return 0;
}